package cn.shujuhai.tsingtu.mhtml2pdf.platform;

import org.openqa.selenium.By;
import org.openqa.selenium.JavascriptExecutor;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.chrome.ChromeOptions;
import org.openqa.selenium.devtools.DevTools;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;

import java.io.File;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.time.Duration;
import java.util.Base64;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class MhtmlToPdfConverter {
    public static void main(String[] args) throws Exception {
        String inputDir = "D:\\DCH\\Download\\SpringBoot";
        String outputDir = "D:\\DCH\\Download\\SpringBoot\\pdfs";

        // 确保输出目录存在
        Files.createDirectories(Paths.get(outputDir));

        System.setProperty("webdriver.chrome.driver", "D:\\DCH\\Download\\chromedriver-win64\\chromedriver.exe");
        ChromeOptions options = new ChromeOptions();
        options.setBinary("D:\\DCH\\Download\\chrome-win64\\chrome.exe");
        options.addArguments(
                "--headless=new",
                "--disable-gpu",
                "--window-size=1920,1080",
                "--no-sandbox",
                "--disable-dev-shm-usage"
        );
        ChromeDriver driver = null;
        try {
            driver = new ChromeDriver(options);
            driver.manage().timeouts().pageLoadTimeout(Duration.ofSeconds(30));

            // 获取DevTools会话
            DevTools devTools = driver.getDevTools();
            devTools.createSession();

            List<Path> files = Files.list(Paths.get(inputDir))
                    .filter(path -> path.toString().endsWith(".mhtml"))
                    .toList();

            for (Path file : files) {
                String outputPdf = outputDir + File.separator
                        + file.getFileName().toString().replace(".mhtml", ".pdf");

                try {
                    // 加载MHTML文件
                    driver.get("file:///" + file.toAbsolutePath().toString().replace("\\", "/"));

                    // 双重等待机制
                    new WebDriverWait(driver, Duration.ofSeconds(30))
                            .until(d -> ((JavascriptExecutor) d)
                                    .executeScript("return document.readyState").equals("complete"));

                    new WebDriverWait(driver, Duration.ofSeconds(30))
                            .until(ExpectedConditions.presenceOfElementLocated(By.tagName("body")));

                    // 执行打印命令并获取数据
                    Map<String, Object> printParams = new HashMap<>();
                    printParams.put("landscape", false);
                    printParams.put("displayHeaderFooter", false);
                    printParams.put("printBackground", true);
                    printParams.put("preferCSSPageSize", true);
                    printParams.put("paperWidth", 8.27);
                    printParams.put("paperHeight", 11.69);
                    printParams.put("transferMode", "ReturnAsBase64");
                    printParams.put("scale", 1.0);

                    Map<String, Object> result = driver.executeCdpCommand("Page.printToPDF", printParams);
                    String pdfData = (String) result.get("data");

                    // 写入文件
                    byte[] pdfBytes = Base64.getDecoder().decode(pdfData);
                    Files.write(Paths.get(outputPdf), pdfBytes);

                    // 验证文件有效性
                    if (Files.size(Paths.get(outputPdf)) == 0) {
                        System.err.println("生成失败：" + outputPdf);
                        continue;
                    }

                    System.out.println("已生成 PDF: " + outputPdf);

                } catch (Exception e) {
                    System.err.println("处理文件 " + file.getFileName() + " 失败: " + e.getMessage());
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            if (driver != null) {
                driver.quit();  // 必须显式调用quit释放资源
            }
        }
    }

}
